/*
 * Copyright 2003-2005 (c) Live Media Pty Ltd. <argot@einet.com.au> 
 *
 * This software is licensed under the Argot Public License 
 * which may be found in the file LICENSE distributed 
 * with this software.
 *
 * More information about this license can be found at
 * http://www.einet.com.au/License
 * 
 * The Developer of this software is Live Media Pty Ltd,
 * PO Box 4591, Melbourne 3001, Australia.  The license is subject 
 * to the law of Victoria, Australia, and subject to exclusive 
 * jurisdiction of the Victorian courts.
 */

#include "Types.h"
 
#include "TypeLibraryTest.h"

#include "TestTypeElement.h"

CPPUNIT_TEST_SUITE_REGISTRATION( TypeLibraryTest );

void TypeLibraryTest::setUp()
{
	type_library_init( &_library ); 
	
	int rc = type_core_init( &_library );
	if ( rc != TYPE_OK )
	{
		printf( "failed to init core" );
	}	
}

void TypeLibraryTest::testCreateTypeLibrary()
{
	type_library library;
	
	type_library_init( &library );
}
    
void TypeLibraryTest::testReserveType() 
{
	type_name name = { "test" };
	
    int id = type_library_reserve( &_library, &name );   
    CPPUNIT_ASSERT( id >= 0 );
    
    CPPUNIT_ASSERT( type_library_get_state( &_library, &name ) == TYPE_RESERVED );
}
    
void TypeLibraryTest::testNotDefinedTypeState()
{
	type_name blah = { "blah" };
	
    int id = type_library_get_state( &_library, &blah );
    
    CPPUNIT_ASSERT( id == TYPE_NOT_DEFINED );
}

void TypeLibraryTest::testRegisterStructure()
{
	type_name test = { "test" };
	test_type_element element;
	test_type_element_init( &element );
	
    int id = type_library_register( &_library, &test, (type_element*) &element );
    CPPUNIT_ASSERT( id >= 0 );

    CPPUNIT_ASSERT( type_library_get_state(&_library, &test) == TYPE_REGISTERED );
}

void TypeLibraryTest::testRegisterComplete()
{
	type_name test = { "test" };
	test_type_element element;
	test_type_element_init( &element );	
	
    int id = type_library_register_bind( &_library, &test, (type_element*) &element, &test_type_element_reader, &test_type_element_writer );
    CPPUNIT_ASSERT( id >= 0 );
    
    CPPUNIT_ASSERT( type_library_get_state( &_library, &test) == TYPE_COMPLETE );
}

void TypeLibraryTest::testRegisterAfterReserve()
{
	type_name test = { "test" };
	test_type_element element;
	test_type_element_init( &element );
		
    type_library_reserve( &_library, &test );
    int id = type_library_register_bind( &_library, &test, (type_element*) &element, &test_type_element_reader, &test_type_element_writer );
    CPPUNIT_ASSERT( id >= 0 );
    
    CPPUNIT_ASSERT( type_library_get_state( &_library, &test ) == TYPE_COMPLETE );
    
    type_element * structure = type_library_get_structure( &_library, type_library_get_id( &_library, &test ));
    CPPUNIT_ASSERT( structure != NULL );
}

void TypeLibraryTest::testBind()
{
	type_name test = { "test" };
	test_type_element element;
	test_type_element_init( &element );
		
    int id = type_library_register( &_library, &test, (type_element*) &element );
    CPPUNIT_ASSERT( id >= 0 );
    
    type_library_bind( &_library, &test, &test_type_element_reader, &test_type_element_writer );
}

void TypeLibraryTest::testBindException()
{
	type_name test = { "test" };

    type_library_bind( &_library, &test, &test_type_element_reader, &test_type_element_writer );
}

void TypeLibraryTest::testGetStructure()
{
	type_name test = { "test" };
	test_type_element element;
	test_type_element_init( &element );
		
    type_library_register_bind( &_library, &test, (type_element*) &element, &test_type_element_reader, &test_type_element_writer );
    
    type_element * elem = type_library_get_structure( &_library, type_library_get_id( &_library, &test));
    CPPUNIT_ASSERT( ((type_element*)&element) == elem );
}
 
void TypeLibraryTest::testGetReader()
{
	type_name test = { "test" };
	test_type_element element;
	test_type_element_init( &element );
	
	typeReader reader = test_type_element_reader;
    type_library_register_bind( &_library, &test, (type_element*) &element, reader, &test_type_element_writer );
    
    typeReader read = type_library_get_reader( &_library, type_library_get_id(&_library, &test));
    CPPUNIT_ASSERT( read == reader );
}

void TypeLibraryTest::testGetReaderFail()
{
	type_name test = { "test" };
	type_name badtype = { "badtype" };
	test_type_element element;
	test_type_element_init( &element );
		
    type_library_register( &_library, &test, (type_element*) &element );
    
    typeReader read = type_library_get_reader( &_library, type_library_get_id( &_library, &test ));
    CPPUNIT_ASSERT( read == NULL );
    
    typeReader reader = type_library_get_reader( &_library, type_library_get_id( &_library, &badtype));
    CPPUNIT_ASSERT( reader == NULL );
            
}

void TypeLibraryTest::testGetWriter()
{
	type_name test = { "test" };	
	test_type_element element;
	test_type_element_init( &element );
		
	typeWriter writer = test_type_element_writer;
    type_library_register_bind( &_library, &test, (type_element*) &element, &test_type_element_reader, writer );
    
    typeWriter write = type_library_get_writer( &_library, type_library_get_id( &_library, &test));
    CPPUNIT_ASSERT( writer == write );
}

void TypeLibraryTest::testGetWriterFail()
{
	type_name test = { "test" };
	type_name badtype = { "badtype" };
	test_type_element element;
	test_type_element_init( &element );
			
    type_library_register( &_library, &test, (type_element*) &element );
    
    typeWriter write = type_library_get_writer( &_library, type_library_get_id( &_library, &test));
    CPPUNIT_ASSERT( write == NULL );
    
    typeWriter writer = type_library_get_writer( &_library, type_library_get_id( &_library, &badtype));
    CPPUNIT_ASSERT( writer == NULL );        
}


void TypeLibraryTest::testRegisterAfterReserveCheckId()
{
	type_name test = { "test" };
	test_type_element element;
	test_type_element_init( &element );
			
    int idres = type_library_reserve( &_library, &test);
    int idreg = type_library_register( &_library, &test, (type_element*) &element );

    CPPUNIT_ASSERT( idres == idreg );
}


void TypeLibraryTest::testNullNameForGetId()
{
    type_library_get_id( &_library, NULL );
}
